#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
租赁合同管理系统 - 全面清理脚本

此脚本用于系统性识别与清理项目中的冗余文件、重复代码块及失效资源，
同时确保删除操作不会对项目核心业务逻辑和功能造成负面影响。
"""

import os
import logging
import shutil
from datetime import datetime

# 配置日志
log_dir = "logs"
os.makedirs(log_dir, exist_ok=True)
log_file = os.path.join(log_dir, f"cleanup_{datetime.now().strftime('%Y%m%d_%H%M%S')}.log")

logging.basicConfig(
    level=logging.INFO,
    format='%(asctime)s [%(levelname)s] %(message)s',
    handlers=[
        logging.FileHandler(log_file),
        logging.StreamHandler()
    ]
)

logger = logging.getLogger("comprehensive_cleanup")

class ProjectCleaner:
    def __init__(self, base_dir):
        """初始化清理器
        
        Args:
            base_dir: 项目根目录
        """
        self.base_dir = base_dir
        self.deleted_files = []
        self.skipped_files = []
        self.errors = []
    
    def delete_file(self, file_path):
        """删除指定文件
        
        Args:
            file_path: 要删除的文件路径
        """
        try:
            if os.path.exists(file_path):
                os.remove(file_path)
                self.deleted_files.append(file_path)
                logger.info(f"已删除文件: {file_path}")
                return True
            else:
                self.skipped_files.append(file_path)
                logger.warning(f"文件不存在，跳过: {file_path}")
                return False
        except Exception as e:
            self.errors.append((file_path, str(e)))
            logger.error(f"删除文件失败: {file_path}, 错误: {str(e)}")
            return False
    
    def delete_directory(self, dir_path):
        """删除指定目录
        
        Args:
            dir_path: 要删除的目录路径
        """
        try:
            if os.path.exists(dir_path) and os.path.isdir(dir_path):
                shutil.rmtree(dir_path)
                self.deleted_files.append(dir_path)
                logger.info(f"已删除目录: {dir_path}")
                return True
            else:
                self.skipped_files.append(dir_path)
                logger.warning(f"目录不存在，跳过: {dir_path}")
                return False
        except Exception as e:
            self.errors.append((dir_path, str(e)))
            logger.error(f"删除目录失败: {dir_path}, 错误: {str(e)}")
            return False
    
    def clean_test_databases(self):
        """清理测试数据库文件"""
        logger.info("开始清理测试数据库文件...")
        
        # 主要测试数据库文件
        db_files = [
            os.path.join(self.base_dir, 'test.db'),
            os.path.join(self.base_dir, 'lease_contract.db'),
            os.path.join(self.base_dir, 'rent_management.db'),
            os.path.join(self.base_dir, 'rent_management.db.backup_1762074876'),
            os.path.join(self.base_dir, 'test_backup_20251102_133158.db'),
            os.path.join(self.base_dir, 'test_backup_20251102_133253.db'),
        ]
        
        for db_file in db_files:
            # 跳过主数据库文件
            if '在用正式版_ZHMY_Contract_SQLite.db' in db_file:
                logger.warning(f"跳过主数据库文件: {db_file}")
                continue
            self.delete_file(db_file)
        
        # 清理备份目录中的测试备份
        backup_dir = os.path.join(self.base_dir, 'backup')
        if os.path.exists(backup_dir):
            test_backups = [
                os.path.join(backup_dir, 'test_backup_20251101_005844.db'),
                os.path.join(backup_dir, 'test_auto_backup_20251101_010555.db'),
                os.path.join(backup_dir, 'test_backup_20251102_133842.db'),
            ]
            
            for backup_file in test_backups:
                self.delete_file(backup_file)
    
    def clean_test_scripts(self):
        """清理测试脚本文件"""
        logger.info("开始清理测试脚本文件...")
        
        test_scripts = [
            os.path.join(self.base_dir, 'test_optimized_logging.py'),
            os.path.join(self.base_dir, 'test_mock_data_generator.py'),
            os.path.join(self.base_dir, 'test_houses_insert.py'),
            os.path.join(self.base_dir, 'test_rent_logic.py'),
            os.path.join(self.base_dir, 'check_test_db.py'),
            os.path.join(self.base_dir, 'test_log_truncation.py'),  # 从日志中发现的测试文件
        ]
        
        for script in test_scripts:
            self.delete_file(script)
    
    def clean_data_fix_scripts(self):
        """清理数据修复和验证脚本"""
        logger.info("开始清理数据修复和验证脚本...")
        
        fix_scripts = [
            os.path.join(self.base_dir, 'verify_negative_fix.py'),
            os.path.join(self.base_dir, 'verify_cleanup.py'),
            os.path.join(self.base_dir, 'verify_rent_data.py'),
            os.path.join(self.base_dir, 'clean_negative_receivables.py'),
            os.path.join(self.base_dir, 'clean_zero_amount_records.py'),
            os.path.join(self.base_dir, 'fix_contract_statuses.py'),
            os.path.join(self.base_dir, 'fix_date_consistency.py'),
            os.path.join(self.base_dir, 'fix_negative_receivable.py'),
            os.path.join(self.base_dir, 'check_negative_receivable.py'),
            os.path.join(self.base_dir, 'check_contract_status.py'),
            os.path.join(self.base_dir, 'check_db_structure.py'),
        ]
        
        for script in fix_scripts:
            self.delete_file(script)
    
    def clean_report_files(self):
        """清理验证报告文件"""
        logger.info("开始清理验证报告文件...")
        
        report_files = [
            os.path.join(self.base_dir, 'verify_zero_amount_report_20251102_133158.txt'),
            os.path.join(self.base_dir, 'verify_zero_amount_report_20251102_133254.txt'),
            os.path.join(self.base_dir, 'cleanup_report_20251102_131946.txt'),
        ]
        
        for report in report_files:
            self.delete_file(report)
    
    def clean_pycache(self):
        """清理__pycache__目录"""
        logger.info("开始清理__pycache__目录...")
        
        pycache_dirs = []
        # 查找所有__pycache__目录
        for root, dirs, files in os.walk(self.base_dir):
            if '__pycache__' in dirs:
                pycache_path = os.path.join(root, '__pycache__')
                pycache_dirs.append(pycache_path)
        
        for pycache_dir in pycache_dirs:
            self.delete_directory(pycache_dir)
    
    def clean_old_logs(self, days_to_keep=7):
        """清理旧日志文件
        
        Args:
            days_to_keep: 保留最近多少天的日志
        """
        logger.info(f"开始清理{days_to_keep}天前的旧日志文件...")
        
        log_dir_path = os.path.join(self.base_dir, 'logs')
        if not os.path.exists(log_dir_path):
            logger.warning("日志目录不存在，跳过日志清理")
            return
        
        current_time = datetime.now()
        
        for filename in os.listdir(log_dir_path):
            file_path = os.path.join(log_dir_path, filename)
            # 跳过当前清理日志文件
            if filename == os.path.basename(log_file):
                continue
            
            try:
                # 获取文件修改时间
                mtime = datetime.fromtimestamp(os.path.getmtime(file_path))
                # 计算文件年龄（天数）
                age_days = (current_time - mtime).days
                
                if age_days > days_to_keep:
                    self.delete_file(file_path)
            except Exception as e:
                self.errors.append((file_path, str(e)))
                logger.error(f"处理日志文件时出错: {file_path}, 错误: {str(e)}")
    
    def generate_cleanup_report(self):
        """生成清理报告"""
        report_path = os.path.join(self.base_dir, f"comprehensive_cleanup_report_{datetime.now().strftime('%Y%m%d_%H%M%S')}.txt")
        
        with open(report_path, 'w', encoding='utf-8') as f:
            f.write(f"租赁合同管理系统 - 全面清理报告\n")
            f.write(f"生成时间: {datetime.now().strftime('%Y-%m-%d %H:%M:%S')}\n")
            f.write(f"项目目录: {self.base_dir}\n\n")
            
            f.write(f"===== 清理结果汇总 =====\n")
            f.write(f"已删除文件数: {len(self.deleted_files)}\n")
            f.write(f"跳过文件数: {len(self.skipped_files)}\n")
            f.write(f"错误文件数: {len(self.errors)}\n\n")
            
            if self.deleted_files:
                f.write(f"===== 已删除文件列表 =====\n")
                for file in self.deleted_files:
                    f.write(f"- {file}\n")
                f.write("\n")
            
            if self.skipped_files:
                f.write(f"===== 跳过文件列表 =====\n")
                for file in self.skipped_files:
                    f.write(f"- {file}\n")
                f.write("\n")
            
            if self.errors:
                f.write(f"===== 错误文件列表 =====\n")
                for file, error in self.errors:
                    f.write(f"- {file}: {error}\n")
                f.write("\n")
        
        logger.info(f"清理报告已生成: {report_path}")
        return report_path
    
    def run(self):
        """执行全面清理"""
        logger.info("开始执行项目全面清理...")
        
        try:
            # 执行各项清理任务
            self.clean_test_databases()
            self.clean_test_scripts()
            self.clean_data_fix_scripts()
            self.clean_report_files()
            self.clean_pycache()
            self.clean_old_logs(days_to_keep=7)
            
            # 生成清理报告
            report_path = self.generate_cleanup_report()
            
            logger.info(f"项目清理完成！")
            logger.info(f"已删除 {len(self.deleted_files)} 个文件/目录")
            logger.info(f"跳过 {len(self.skipped_files)} 个不存在的文件/目录")
            logger.info(f"处理过程中出现 {len(self.errors)} 个错误")
            logger.info(f"详细报告请查看: {report_path}")
            
            return True
        except Exception as e:
            logger.error(f"清理过程中发生未预期的错误: {str(e)}")
            return False

if __name__ == "__main__":
    # 获取脚本所在目录作为项目根目录
    BASE_DIR = os.path.dirname(os.path.abspath(__file__))
    
    logger.info(f"开始清理项目: {BASE_DIR}")
    
    # 创建清理器实例并运行
    cleaner = ProjectCleaner(BASE_DIR)
    success = cleaner.run()
    
    if success:
        logger.info("项目清理成功完成！")
    else:
        logger.error("项目清理过程中出现错误，请查看日志获取详细信息")
